#ifndef __MINIUTIL_MULTINET_LENMSGREADER_H__
#define __MINIUTIL_MULTINET_LENMSGREADER_H__

#include "miniutil/socketmultiplex.h"

namespace miniutil { namespace multinet {

class LenMsgSource
{
    public:
        virtual int Recv(char* pbuf, int len) = 0;
};

class LenMsgSource_Soc:public LenMsgSource
{
    public:
        LenMsgSource_Soc(SOCKET soc);
        virtual int Recv(char* pbuf, int len);
    private:
        SOCKET msoc;
};

class LenMsgSource_Sms:public LenMsgSource
{
    public:
        LenMsgSource_Sms(miniutil::multinet::SocketMulplexService* pse, SOCKET soc);
        virtual int Recv(char* pbuf, int len);
    private:
        miniutil::multinet::SocketMulplexService* mpss;
        SOCKET msoc;
};

class LenMsgSource_Fifo:public LenMsgSource
{
    public:
        LenMsgSource_Fifo(miniutil::data::fifobuf *pfifo);
        virtual int Recv(char* pbuf, int len);
    private:
        miniutil::data::fifobuf *mpfifo;
};

class LenMsgReader
{
	public:
        LenMsgReader(int offset = 0, int size = 4);
        ~LenMsgReader();
        int Read(SOCKET soc);
        int Read(miniutil::multinet::SocketMulplexService* pse, SOCKET soc); //0, not finished, 1 finished, -1 fail
        int Read(miniutil::data::fifobuf* pfifo);
        int Clear();
        int GetMsgBufLen();
        char* RefMsgBuf();
    private:
        int Read(LenMsgSource* psrc);
        
        unsigned int msglen;
        int msghaveread;
        char * pbuf;
        
        char tmpbuf[128];
        
        int mlenoffset; //the offset of len id
        int mlensize;   //the byte num of len id
};

} }	

#endif
